package fengxici.jframe4l;


import org.reactivestreams.Publisher;
import org.redisson.Redisson;
import org.redisson.api.*;
import org.redisson.config.Config;
import org.redisson.config.TransportMode;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.List;
import java.util.Map;

/**
 * Hello world!
 */
public class App {
    public static void main(String[] args) {
        try {
            String basePath = App.class.getClass().getResource("/").getPath();
            /////////////// Programmatic configuration////////////////////
//            System.out.println("Hello World!");
//            Config config = new Config();
//            config.setTransportMode(TransportMode.EPOLL);
//            config.useClusterServers()
//                    .addNodeAddress("redis://127.0.0.1:6397");
//            RedissonClient redisson = Redisson.create(config);
//            System.out.println(config.toJSON());
            ////////////// json file based configuration//////////////////
            Config jsonConfig = Config.fromJSON(new File(basePath+"\\config-file.json"));
            RedissonClient jsonClient = Redisson.create(jsonConfig);
            System.out.println(jsonConfig.toJSON());
            ///////////////yaml file based configuration/////////////////
            Config ymalConfig = Config.fromYAML(new File(basePath+"\\config-file.yaml"));
            RedissonClient ymalClient = Redisson.create(ymalConfig);

          //程序接口调用方式
            RAtomicLong longObject = jsonClient.getAtomicLong("myLong");
            //同步执行方式
            longObject.compareAndSet(3,401);
            //异步执行方式
            RFuture<Boolean> future =longObject.compareAndSetAsync(3,401);
            future.whenComplete((res, exception) -> {
               System.out.println(res);
               System.out.println(exception.getMessage());
            });
            RedissonReactiveClient reactiveClient = Redisson.createReactive(jsonConfig);
            RAtomicLongReactive reactiveLongObject = reactiveClient.getAtomicLong("myReactiveLong");
            //异步流执行方式
            reactiveLongObject.compareAndSet(3,401);
            Publisher<Boolean> csPublisher = reactiveLongObject.compareAndSet(10, 91);
            Publisher<Long> getPublisher = reactiveLongObject.get();
            //分布式对象
            RKeys keys = jsonClient.getKeys();
            Iterable<String> allKeys = keys.getKeys();
            Iterable<String> foundedKeys = keys.getKeysByPattern("key*");
            long numOfDeletedKeys = keys.delete("obj1", "obj2", "obj3");
            long deletedKeysAmount = keys.deleteByPattern("test?");
            String randomKey = keys.randomKey();
            long keysAmount = keys.count();
            //通用桶对象
            RBucket<Long> bucket = jsonClient.getBucket("anyObject");
            bucket.set(new Long(1));
            Object obj = bucket.get();
            bucket.trySet(new Long(3));
            bucket.compareAndSet(new Long(4), new Long(5));
            bucket.getAndSet(new Long(6));
            //二进制流
            RBinaryStream stream = jsonClient.getBinaryStream("anyStream");
            byte[] content = "hello redisson".getBytes();
            stream.set(content);
            InputStream is = stream.getInputStream();
            byte[] readBuffer = new byte[512];
            is.read(readBuffer);
            OutputStream os = stream.getOutputStream();
            byte[] contentToWrite = "hello redis".getBytes();
            os.write(contentToWrite);
            //地理空间对象桶
            RGeo<String> geo = jsonClient.getGeo("test");
            geo.add(new GeoEntry(13.361389, 38.115556, "Palermo"),
                    new GeoEntry(15.087269, 37.502669, "Catania"));
            geo.addAsync(37.618423, 55.751244, "Moscow");
            Double distance = geo.dist("Palermo", "Catania", GeoUnit.METERS);
            geo.hashAsync("Palermo", "Catania");
            Map<String, GeoPosition> positions = geo.pos("test2", "Palermo", "test3", "Catania", "test1");
            List<String> cities = geo.radius(15, 37, 200, GeoUnit.KILOMETERS);
            Map<String, GeoPosition> citiesWithPositions = geo.radiusWithPosition(15, 37, 200, GeoUnit.KILOMETERS);
            //BitSet
            RBitSet set = jsonClient.getBitSet("simpleBitset");
            set.set(0, true);
            set.set(1812, false);
            set.clear(0);
            set.xor("anotherBitset");
            //原子整长型
            RAtomicLong atomicLong = jsonClient.getAtomicLong("myAtomicLong");
            atomicLong.set(3);
            atomicLong.incrementAndGet();
            atomicLong.get();
            //双精度浮点
            RAtomicDouble atomicDouble = jsonClient.getAtomicDouble("myAtomicDouble");
            atomicDouble.set(2.81);
            atomicDouble.addAndGet(4.11);
            atomicDouble.get();
            //布隆过滤器
            RBloomFilter<User> bloomFilter = jsonClient.getBloomFilter("sample");
            // 初始化布隆过滤器，预计统计元素数量为55000000，期望误差率为0.03
            bloomFilter.tryInit(55000000L, 0.03);
            bloomFilter.add(new User("field1Value", "field2Value"));
            bloomFilter.add(new User("field5Value", "field8Value"));
            bloomFilter.contains(new User("field1Value", "field8Value"));
            //基数估算法
            RHyperLogLog<Integer> log = jsonClient.getHyperLogLog("log");
            log.add(1);
            log.add(2);
            log.add(3);
            log.count();
            //整长累加器
            RLongAdder atomicLongAdder = jsonClient.getLongAdder("myLongAdder");
            atomicLongAdder.add(12);
            atomicLongAdder.increment();
            atomicLongAdder.decrement();
            atomicLongAdder.sum();

            /////////////映射map//////////////////////
            RMap<String, Long> map = jsonClient.getMap("anyMap");
            Long prevObject = map.put("123", 123l);
            Long currentObject = map.putIfAbsent("323", 323l);
            Long removeObj = map.remove("123");

            map.fastPut("321", 321l);
            map.fastRemove("321");

            RFuture<Long> putAsyncFuture = map.putAsync("321",321l);
            RFuture<Boolean> fastPutAsyncFuture = map.fastPutAsync("321",321l);

            map.fastPutAsync("321", 321l);
            map.fastRemoveAsync("321");

            //////////////////映射的字段锁/////////////////////////////////
            RMap<String, Long> mapLock = jsonClient.getMap("anyMap");
            String k = new String("123");
            RLock keyLock = mapLock.getLock(k);
            keyLock.lock();
            try {
                Long v = map.get(k);
                // 其他业务逻辑
            } finally {
                keyLock.unlock();
            }

            RReadWriteLock rwLock = map.getReadWriteLock(k);
            rwLock.readLock().lock();
            try {
                Long v = map.get(k);
                // 其他业务逻辑
            } finally {
                rwLock.readLock().unlock();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
